﻿#region Copyright (c) 2000-2013 Developer Express Inc.
/*
{*******************************************************************}
{                                                                   }
{       Developer Express .NET Component Library                    }
{                                                                   }
{                                                                   }
{       Copyright (c) 2000-2013 Developer Express Inc.              }
{       ALL RIGHTS RESERVED                                         }
{                                                                   }
{   The entire contents of this file is protected by U.S. and       }
{   International Copyright Laws. Unauthorized reproduction,        }
{   reverse-engineering, and distribution of all or any portion of  }
{   the code contained in this file is strictly prohibited and may  }
{   result in severe civil and criminal penalties and will be       }
{   prosecuted to the maximum extent possible under the law.        }
{                                                                   }
{   RESTRICTIONS                                                    }
{                                                                   }
{   THIS SOURCE CODE AND ALL RESULTING INTERMEDIATE FILES           }
{   ARE CONFIDENTIAL AND PROPRIETARY TRADE                          }
{   SECRETS OF DEVELOPER EXPRESS INC. THE REGISTERED DEVELOPER IS   }
{   LICENSED TO DISTRIBUTE THE PRODUCT AND ALL ACCOMPANYING .NET    }
{   CONTROLS AS PART OF AN EXECUTABLE PROGRAM ONLY.                 }
{                                                                   }
{   THE SOURCE CODE CONTAINED WITHIN THIS FILE AND ALL RELATED      }
{   FILES OR ANY PORTION OF ITS CONTENTS SHALL AT NO TIME BE        }
{   COPIED, TRANSFERRED, SOLD, DISTRIBUTED, OR OTHERWISE MADE       }
{   AVAILABLE TO OTHER INDIVIDUALS WITHOUT EXPRESS WRITTEN CONSENT  }
{   AND PERMISSION FROM DEVELOPER EXPRESS INC.                      }
{                                                                   }
{   CONSULT THE END USER LICENSE AGREEMENT FOR INFORMATION ON       }
{   ADDITIONAL RESTRICTIONS.                                        }
{                                                                   }
{*******************************************************************}
*/
#endregion Copyright (c) 2000-2013 Developer Express Inc.

using System;
using System.Collections.Generic;
using System.Reflection;
using System.Windows;
using System.Windows.Data;
using System.Windows.Interop;
using System.Windows.Media;
using UColor.Core;
using UColor.Core.Parts;
using UColor.Core.Helpers;
using DevExpress.Utils;
using DevExpress.Xpf.Core;
using UColor.WPF.Helpers;
using UColor.WPF.Internal;
namespace UColor.WPF {
    public abstract class DemoStartup : UCStartupBase
    {
		const string MenuString = "Menu=";
		const string MainMenuString = "MainMenu";
		const string EmptyLocationString = "Empty";
		public static StartupBase DemoLauncherRun(Assembly demoAssembly, string moduleName, UIElement page, Action onModuleLoaded) {
			MethodInfo runMethod = typeof(StartupBase).GetMethod("Run", BindingFlags.Static | BindingFlags.Public, null, new Type[] { typeof(Application), typeof(bool), typeof(bool), typeof(UIElement), typeof(object) }, null);
			runMethod = runMethod.MakeGenericMethod(DemoHelper.GetStartup(demoAssembly));
			DemoStartup startup = (DemoStartup)runMethod.Invoke(null, new object[] { Application.Current, false, false, page, moduleName });
			if(onModuleLoaded != null)
				startup.ModuleLoaded += (s, e) => onModuleLoaded();
			return startup;
		}
		static readonly string CommonXamlPath = XamlReaderHelper.GetXamlPath("Themes/Common.xaml");
		ResourceDictionary demoCommonXaml;
		bool isModuleLoaded = false;
		//BookmarkHelper bookmarkHelper;
		static DemoStartup() {
			DemoThemeName = "Demo";
			ThemeHelper.SetActualThemeName(DemoThemeName, Theme.MetropolisLight.Name);
			DefaultTheme = Theme.MetropolisLight;
		}
		public DemoStartup() {

		    Title = "UColor";

		}
		public Assembly DemoAssembly { get; private set; }
		public bool Debug { get; private set; }
		public event EventHandler ModuleLoaded;
		protected bool RunFromDemoLauncher { get { return UserData != null; } }
		protected override bool DoStartup() {
			ThemeManager.ApplicationThemeName = GetDefaultTheme().Name;
			if(!base.DoStartup()) return false;
			ExitAtRequest = true;
			DemoAssembly = GetAssembly();
			Icon = GetIcon();
			Debug = GetDebug();
           
			return true;
		}
		protected override UIElement CreateMainElement() {
			InitDemo();
			DemoBase = new Base(DemoAssembly, UserData as string);
			DemoBase.DemoBaseControl.AllowRunAnotherDemo = RunFromDemoLauncher;
			DemoBase.DemoBaseControl.State.PageChanged += OnDemoBaseControlStatePageChanged;
			DemoBase.DemoBaseControl.State.ModuleIDChanged += OnDemoBaseControlStateModuleIDChanged;
			//DemoBase.DemoBaseControl.Data.ProductsChanged += OnDemoBaseControlMainProductModulesChanged;
			BindingOperations.SetBinding(this, TitleProperty, new Binding("Title.TextAsync") { Source = DemoBase, Mode = BindingMode.OneWay });
			return DemoBase.DemoBaseControl;
		}
        //void OnDemoBaseControlMainProductModulesChanged(object sender, ThePropertyChangedEventArgs<System.Collections.ObjectModel.ReadOnlyCollection<ProductDescription>> e) {
        //    //DemoBase.DemoBaseControl.Data.ProductsChanged -= OnDemoBaseControlMainProductModulesChanged;
        //    BackgroundHelper.DoInBackground(null, () => {
        //        bookmarkHelper = new BookmarkHelper(this, EmptyLocationString);
        //        bookmarkHelper.CurrentStateChanged += OnBookmarkHelperCurrentStateChanged;
        //        string initialState = GetState();
        //        bookmarkHelper.SetRedirect(string.Empty, initialState);
        //        string currentState = bookmarkHelper.CurrentState;
        //        if(string.IsNullOrEmpty(currentState)) {
        //            bookmarkHelper.CurrentState = initialState;
        //        } else {
        //            OnBookmarkHelperCurrentStateChanged(bookmarkHelper, EventArgs.Empty);
        //        }
        //    }, 300);
        //}
		void UpdateCurrentState() {
            //if(bookmarkHelper == null) return;
            //string currentState = GetState();
            //if(!string.IsNullOrEmpty(currentState)) {
            //    bookmarkHelper.CurrentState = currentState;
            //}
		}
		void OnDemoBaseControlStateModuleIDChanged(object sender, ThePropertyChangedEventArgs<object> e) {
			UpdateCurrentState();
		}
		void OnBookmarkHelperCurrentStateChanged(object sender, EventArgs e) {
			string currentState = ((BookmarkHelper)sender).CurrentState;
			if(string.IsNullOrEmpty(currentState) || currentState == EmptyLocationString) return;
			if(GetIsMainMenuBookmark(currentState)) {
				DemoBase.DemoBaseControl.State.Page = BaseControlPage.ModulesPage;
			} else {
				string demoName = GetDemoNameBookmark(currentState);
				if(string.IsNullOrEmpty(demoName)) {
					SetCurrentModule(currentState);
				} else {
					SetCurrentProduct(demoName);
				}
			}
		}
		string GetState() {
			if(DemoBase.DemoBaseControl.State.Page == BaseControlPage.ModulesPage) {
				return MainMenuString;
			} else {
				if(DemoBase.DemoBaseControl.State.Page == BaseControlPage.ModulesPage) {
					//return DemoBase.DemoBaseControl.State.ProductID == null || DemoBase.DemoBaseControl.Data.Products == null ? string.Empty : MenuString + DemoBase.DemoBaseControl.Data.GetProduct(DemoBase.DemoBaseControl.State.ProductID).Name;
                    return "";
				} else {
					//if(DemoBase.DemoBaseControl.State.ModuleID == null || DemoBase.DemoBaseControl.Data.Products == null) return string.Empty;

                    return "";
				}
			}
		}
		bool GetIsMainMenuBookmark(string value) {
			return value == MainMenuString;
		}
		string GetDemoNameBookmark(string value) {
			return value.Contains(MenuString) ? value.Replace(MenuString, string.Empty) : null;
		}
		void SetCurrentModule(string newValue) {
            //if(newValue.Contains(MainMenuString) || newValue.Contains(MenuString)) return;
            //if(product == DemoBase.DemoBaseControl.Data.MainProduct) {
            //    product = DemoBase.DemoBaseControl.Data.MainProduct;
            //}
            //if(product.Modules == null) {
            //    product.ModulesChanged += OnCurrentProductModulesChanged;
            //} else {
            //    //DemoBase.SetModuleID(product.GetModuleIDByName(newValue));
            //}
		}
		void SetCurrentProduct(string newValue) {
			DemoBase.DemoBaseControl.State.Page = BaseControlPage.ModulesPage;
			
		}
		
		void OnDemoBaseControlStatePageChanged(object sender, ThePropertyChangedEventArgs<BaseControlPage> e) {
			if(e.NewValue == BaseControlPage.MainPage && !isModuleLoaded) {
				isModuleLoaded = true;
				if(ModuleLoaded != null)
					ModuleLoaded(this, EventArgs.Empty);
			}
			UpdateCurrentState();
		}
		protected virtual ImageSource GetIcon() {
#if SL
			return null;
#else
			return ImageSourceHelper.GetImageSource(AssemblyHelper.GetResourceUri(GetAssembly(), "demoicon.ico"));
#endif
		}
		protected virtual Assembly GetAssembly() { return GetType().Assembly; }
		protected abstract bool GetDebug();
		public static Theme DefaultTheme { get; set; }
		public static Theme DemoTheme { get { return Theme.FindTheme(DemoThemeName); } }
		public static string DemoThemeName { get; set; }
		public Base DemoBase { get; private set; }
		protected override void OnRootVisualLoaded(object sender, RoutedEventArgs e) {
			base.OnRootVisualLoaded(sender, e);
#if SL
			FrameworkElement root = Application.Current == null ? null : (FrameworkElement)Application.Current.RootVisual;
#else
			FrameworkElement root = Application.Current == null ? null : (FrameworkElement)Application.Current.MainWindow;
#endif
			if(root == null) return;

		}
		protected virtual Type GetFixtureTypeForXBAPOrSLTesting() { return null; }
		static Theme GetDefaultTheme() {
			return DefaultTheme == null ? Theme.Default : DefaultTheme;
		}
		void InitDemo() {
			if(AssemblyHelper.GetResourceStream(DemoAssembly, CommonXamlPath, true) != null)
				this.demoCommonXaml = new ResourceDictionary() { Source = AssemblyHelper.GetResourceUri(DemoAssembly, CommonXamlPath) };
			else
				this.demoCommonXaml = null;
			if(this.demoCommonXaml != null)
				Application.Current.Resources.MergedDictionaries.Add(this.demoCommonXaml);
			Type appType = DemoHelper.GetStartup(DemoAssembly);
			MethodInfo mi = appType.GetMethod("InitDemo", BindingFlags.Static | BindingFlags.Public);
			if(mi != null)
				mi.Invoke(null, new object[] { });
		}
		void ClearDemo() {
			if(DemoAssembly != null) {
				Type appType = DemoHelper.GetStartup(DemoAssembly);
				MethodInfo mi = appType.GetMethod("ClearDemo", BindingFlags.Static | BindingFlags.Public);
				if(mi != null)
					mi.Invoke(null, new object[] { });
			}
			if(this.demoCommonXaml != null)
				Application.Current.Resources.MergedDictionaries.Remove(this.demoCommonXaml);
		}
	}
}
